/*
 * Licensed to the Apache Software Foundation (ASF) under one
 * or more contributor license agreements.  See the NOTICE file
 * distributed with this work for additional information
 * regarding copyright ownership.  The ASF licenses this file
 * to you under the Apache License, Version 2.0 (the
 * "License"); you may not use this file except in compliance
 * with the License.  You may obtain a copy of the License at
 *
 *     http://www.apache.org/licenses/LICENSE-2.0
 *
 * Unless required by applicable law or agreed to in writing,
 * software distributed under the License is distributed on an
 * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
 * KIND, either express or implied.  See the License for the
 * specific language governing permissions and limitations
 * under the License.
 */

/**
 * @Title: AppConfig.java
 * @Package phoenics.apeak.crawl.config
 * @Description
 * @author phoenics@126com
 * @date 2016-1-30 16:01:32
 * @version V1.0
 */
package phoenics.apeak.crawl.config;


import java.util.concurrent.ExecutorService;
import java.util.concurrent.Executors;

import org.eclipse.jetty.client.HttpClient;
import org.eclipse.jetty.util.ssl.SslContextFactory;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.ComponentScan;
import org.springframework.context.annotation.Configuration;

import com.lmax.disruptor.BlockingWaitStrategy;
//import com.lmax.disruptor.BusySpinWaitStrategy;
import com.lmax.disruptor.EventFactory;
import com.lmax.disruptor.dsl.Disruptor;
import com.lmax.disruptor.dsl.ProducerType;

import phoenics.apeak.crawl.Document;
import phoenics.apeak.crawl.DocumentHandle;
import phoenics.apeak.crawl.FinishHandle;

// TODO: Auto-generated Javadoc
/**
 * The Class AppConfig.
 *
 * @Description The Class AppConfig.
 */
@Configuration
@ComponentScan(basePackages = {"phoenics.apeak.crawl"})
public class AppConfig {
	
	/** The executor. */
	private ExecutorService  executor=Executors.newFixedThreadPool(8);  
	
	/** The http client_. */
	private  HttpClient httpClient_ =null;
	
	/**
 * Executor service.
 *
 * @return the executor service
 * @throws Exception
 *             the exception
 * @Description Executor service.
 */
	@Bean
	public ExecutorService executorService()  throws Exception {
		return executor;  
	}
	
	/**
 * Http client.
 *
 * @return the http client
 * @throws Exception
 *             the exception
 * @Description Http client.
 */
	@Bean
	   public HttpClient httpClient ()  throws Exception {
		if(this.httpClient_!=null){
			return this.httpClient_;
		}
		SslContextFactory sslContextFactory = new SslContextFactory();
		HttpClient httpClient_ =new HttpClient(sslContextFactory);
		httpClient_.setFollowRedirects(false);
		httpClient_.setExecutor(executorService());
		httpClient_.setIdleTimeout(10*1000);
		httpClient_.setRemoveIdleDestinations(true);
		//httpClient_.setAddressResolutionTimeout(7*1000);
		httpClient_.setMaxConnectionsPerDestination(50*5);
		httpClient_.start();
		this.httpClient_=httpClient_;
		return httpClient_;
	   }
	   
   	/**
 * Disruptor.
 *
 * @return the disruptor
 * @throws Exception
 *             the exception
 * @Description 配置Disruptor.,使用单个线程处理所有请求
 */
   	@SuppressWarnings("unchecked")
	@Bean
	   public  Disruptor<Document> disruptor() throws Exception {
			 int bufferSize=8*1024;  
			 ExecutorService  myExecutor=Executors.newFixedThreadPool(4);
		      Disruptor<Document> disruptor=new Disruptor<Document>(new EventFactory<Document>() {  
		            @Override  
		            public Document newInstance() {  
		                return new Document();  
		            }  
		        }, bufferSize,  myExecutor, ProducerType.SINGLE, new BlockingWaitStrategy());  
		      disruptor.handleEventsWith(new DocumentHandle(httpClient ())).then(new FinishHandle());
		      disruptor.start();
		   return disruptor;
	   }
	   

}